package com.example.net;

import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.sql.Timestamp;
import java.util.Date;

public class KunSocket {

	private String ip = "";
	private int port = 9090;
	private Socket mSocket;
	private InputStream in;
	private OutputStream out;
	private volatile boolean isCon = false;
	private volatile boolean isRec = false;
	private RecHandler recHandler;
	private static volatile boolean isOnline = false;
	private volatile Date startDate ,endDate;
	private int ticker = 0;
	public KunSocket(){};
	
	public KunSocket(String Ip,int port,RecHandler recHandler ){
		this.ip = Ip;
		this.port = port;
		this.recHandler = recHandler;
		mheart.start();
	}
	
	public void setIp(String ip , int port){
		this.ip = ip;
		this.port = port;
	}
	
	public void connect(){
		
		new Thread(new Runnable() {
			
			@Override
			public void run() {
				// TODO Auto-generated method stub
				try {
					isCon = true;
					mSocket = new Socket();
					mSocket.connect(new InetSocketAddress(ip,port));
					mSocket.setSoTimeout(3000);
					in = mSocket.getInputStream();
					out = mSocket.getOutputStream();
					isRec = true;
					isOnline = true;
					Start_Reciver();
					ticker = 0;
					if(recHandler!=null)
					recHandler.ConnectSucceeful();
				} catch (Exception e) {
					// TODO: handle exception
					try {
						Thread.sleep(1000);
					} catch (InterruptedException e1) {
						// TODO Auto-generated catch block
						e1.printStackTrace();
					}
					isCon = false;
					if(recHandler!=null)
						recHandler.DisConnect();
				}
			}
		}).start();
	}
	
	private void Start_Reciver(){
		if(!isCon)
			return;
		new Thread(new Runnable() {
			
			@Override
			public void run() {
				// TODO Auto-generated method stub
				while(isRec){
					try {
						int len = -1;
						byte[] recByte = new byte[128];
						ByteArrayOutputStream bos = new ByteArrayOutputStream();
						len = in.read(recByte);
						
						if(len == -1){
							
							continue;
						}
						isOnline = true;
						endDate = new Date(System.currentTimeMillis());
						bos.write(recByte, 0, len);
						bos.close();
						byte[] doByte = bos.toByteArray();
						sendMsg("state:"+isOnline);
						if(recHandler != null){
							recHandler.doRecData(doByte);
						}
					} catch (Exception e) {
						// TODO: handle exception
						e.printStackTrace();
					}
					
				}
			}
		}).start();
	}
	
	Thread mheart = new Thread(new Runnable() {
		
		@Override
		public void run() {
			// TODO Auto-generated method stub
			while(true){
				try{
					startDate = new Date(System.currentTimeMillis());
					isOnline = false;
					sendMsg("{cmd0#}");
					Thread.sleep(1000 * 4);
				}catch(Exception e){
					sendMsg(e.toString());
				}
				sendMsg("threadState:"+isOnline);
				if(isCon)
				if(!isOnline){
					ticker  ++ ;
					if(ticker >= 3){
						reCon();
						
					}
					
				}else{
					ticker = 0;
				}
				
			}
			
			
			
		}
	});
	
	public void sendMsg(final String str){

		if(out == null)
			return ;
		new Thread(new Runnable() {
			
			@Override
			public void run() {
				// TODO Auto-generated method stub
				try {
					
						byte[] sendBuff = str.getBytes("utf-8");
						out.write(sendBuff);
						out.flush();
					
					
				} catch (Exception e) {
					// TODO: handle exception
					e.printStackTrace();
				}
			}
		}).start();
	}
	
	public synchronized void reCon(){
		close();
		recHandler.DisConnect();
		connect();
	}
	
	public void close(){
		try {
			ticker = 1;
			isCon = false;
			in.close();
			out.close();
			mSocket.close();
		} catch (Exception e) {
			// TODO: handle exception
		}
	}
	
	public  interface RecHandler{
		public void doRecData(byte[] recBuff);
		public void DisConnect();
		public void ConnectSucceeful();
	}
	
	
}
